home *** CD-ROM | disk | FTP | other *** search
/ Atari Mega Archive 1 / Atari Mega Archive - Volume 1.iso / language / asxsrc.arc / ASSYM.C < prev    next >
C/C++ Source or Header  |  1991-06-10  |  4KB  |  241 lines

  1. /* assym.c */
  2.  
  3. /*
  4.  * (C) Copyright 1989
  5.  * All Rights Reserved
  6.  *
  7.  * Alan R. Baldwin
  8.  * 721 Berkeley St.
  9.  * Kent, Ohio  44240
  10.  */
  11.  
  12. #include <stdio.h>
  13. #include <setjmp.h>
  14. #include "asm.h"
  15.  
  16. /*
  17.  * This routine is called early in the
  18.  * game to set up the hashtables. First
  19.  * all buckets in a table are cleared.
  20.  * Then a pass is made through the respective
  21.  * symbol lists, linking them into their hash
  22.  * buckets. Finally the area list and
  23.  * 'dca' are set up.
  24.  */
  25. VOID
  26. syminit()
  27. {
  28.     register struct mne  *mp;
  29.     struct mne **mpp;
  30.     register struct sym  *sp;
  31.     struct sym **spp;
  32.     register h;
  33.  
  34.     mpp = &mnehash[0];
  35.     while (mpp < &mnehash[NHASH])
  36.         *mpp++ = NULL;
  37.     mp = &mne[0];
  38.     for (;;) {
  39.         h = hash(mp->m_id);
  40.         mp->m_mp = mnehash[h];
  41.         mnehash[h] = mp;
  42.         if (mp->m_flag&S_END)
  43.             break;
  44.         ++mp;
  45.     }
  46.  
  47.     spp = &symhash[0];
  48.     while (spp < &symhash[NHASH])
  49.         *spp++ = NULL;
  50.     sp = &sym[0];
  51.     for (;;) {
  52.         h = hash(sp->s_id);
  53.         sp->s_sp = symhash[h];
  54.         symhash[h] = sp;
  55.         if (sp->s_flag&S_END)
  56.             break;
  57.         ++sp;
  58.     }
  59.  
  60.     areap = dca;
  61. }
  62.  
  63. /*
  64.  * Lookup the area `id'.
  65.  */
  66. struct area *
  67. alookup(id)
  68. char *id;
  69. {
  70.     register struct area *ap;
  71.  
  72.     ap = areap;
  73.     while (ap) {
  74.         if (symeq(id, ap->a_id)) {
  75.             return (ap);
  76.         }
  77.         ap = ap->a_ap;
  78.     }
  79.     return(NULL);
  80. }
  81.  
  82. /*
  83.  * Lookup the mnemonic (or directive) `id' in the hashtable.
  84.  * If it is not found return a NULL.
  85.  */
  86. struct mne *
  87. mlookup(id)
  88. char *id;
  89. {
  90.     register struct mne *mp;
  91.     register h;
  92.  
  93.     h = hash(id);
  94.     mp = mnehash[h];
  95.     while (mp) {
  96.         if (symeq(id, mp->m_id))
  97.             return (mp);
  98.         mp = mp->m_mp;
  99.     }
  100.     return (NULL);
  101. }
  102.  
  103. /*
  104.  * Lookup the label `id' in the hashtable.
  105.  * If it is not found either return a
  106.  * pointer to a newly created hash table
  107.  * entry.
  108.  */
  109. struct sym *
  110. lookup(id)
  111. char *id;
  112. {
  113.     register struct sym *sp;
  114.     register h;
  115.  
  116.     h = hash(id);
  117.     sp = symhash[h];
  118.     while (sp) {
  119.         if (symeq(id, sp->s_id))
  120.             return (sp);
  121.         sp = sp->s_sp;
  122.     }
  123.     sp = (struct sym *) new (sizeof(struct sym));
  124.     sp->s_sp = symhash[h];
  125.     symhash[h] = sp;
  126.     sp->s_tsym = NULL;
  127.     sp->s_type = S_NEW;
  128.     sp->s_area = NULL;
  129.     strncpy(sp->s_id, id, NCPS);
  130.     return (sp);
  131. }
  132.  
  133. /*
  134.  * Mark all symbols of type `S_NEW' global.
  135.  * Called at the beginning of pass 1 if '-g'.
  136.  */
  137. VOID
  138. symglob()
  139. {
  140.     register struct sym *sp;
  141.     register i;
  142.  
  143.     for (i=0; i<NHASH; ++i) {
  144.         sp = symhash[i];
  145.         while (sp != NULL) {
  146.             if (sp->s_type == S_NEW)
  147.                 sp->s_flag |= S_GBL;
  148.             sp = sp->s_sp;
  149.         }
  150.     }
  151. }
  152.  
  153. /*
  154.  * Mark all symbols of type `S_USER' global.
  155.  * Called at the beginning of pass 1 if '-a'.
  156.  */
  157. VOID
  158. allglob()
  159. {
  160.     register struct sym *sp;
  161.     register i;
  162.  
  163.     for (i=0; i<NHASH; ++i) {
  164.         sp = symhash[i];
  165.         while (sp != NULL) {
  166.             if (sp != dot && sp->s_type == S_USER)
  167.                 sp->s_flag |= S_GBL;
  168.             sp = sp->s_sp;
  169.         }
  170.     }
  171. }
  172.  
  173. /*
  174.  * Compare two symbol names.
  175.  */
  176. int
  177. symeq(p1, p2)
  178. register char *p1, *p2;
  179. {
  180.     register n;
  181.  
  182.     n = NCPS;
  183.     do {
  184.  
  185. #if    CASE_SENSITIVE
  186.         if (*p1++ != *p2++)
  187.             return (0);
  188. #else
  189.         if (ccase[*p1++] != ccase[*p2++])
  190.             return (0);
  191. #endif
  192.  
  193.     } while (--n);
  194.     return (1);
  195. }
  196.  
  197. /*
  198.  * Given a pointer to a symbol name
  199.  * compute and return the hash table
  200.  * bucket.
  201.  * The `sum of all the characters mod
  202.  * table size' algorithm is perhaps
  203.  * not the best.
  204.  */
  205. int
  206. hash(p)
  207. register char *p;
  208. {
  209.     register h, n;
  210.  
  211.     h = 0;
  212.     n = NCPS;
  213.     do {
  214.  
  215. #if    CASE_SENSITIVE
  216.         h += *p++;
  217. #else
  218.         h += ccase[*p++];
  219. #endif
  220.  
  221.     } while (--n);
  222.     return (h&HMASK);
  223. }
  224.  
  225. /*
  226.  * Allocate a block of space.
  227.  * Leave if there is no space left
  228.  * at all.
  229.  */
  230. VOID *
  231. new(n)
  232. {
  233.     register VOID *p;
  234.  
  235.     if ((p = (VOID *) calloc(1,n)) == NULL) {
  236.         fprintf(stderr, "Out of space!\n");
  237.         exit(1);
  238.     }
  239.     return (p);
  240. }
  241.